﻿using Microsoft.AspNetCore.Http;
using System.IdentityModel.Tokens.Jwt;
using System.Net;
using System.Security.Claims;

namespace Common.Jwt
{
    public static class JwtHelper
    {
        /// <summary>
        /// 获取token
        /// </summary>
        /// <returns></returns>
        public static string GetJwtToken()
        {
            var claims = new List<Claim>();
            var jwtSecurityToken = new JwtSecurityToken(
                    JwtConfig.Instance.Issuer,
                    JwtConfig.Instance.Audience,
                    claims,
                    JwtConfig.Instance.NotBefore,
                    JwtConfig.Instance.Expiration,
                    JwtConfig.Instance.SigningCredentials
                );
            var token = new JwtSecurityTokenHandler().WriteToken(jwtSecurityToken);
            token = "Bearer " + token;
            return token;
        }
        /// <summary>
        /// 添加claims信息
        /// </summary>
        /// <param name="claims"></param>
        /// <returns></returns>
        public static string GetJwtToken(List<Claim> claims)
        {
            var jwtSecurityToken = new JwtSecurityToken(
                    JwtConfig.Instance.Issuer,
                    JwtConfig.Instance.Audience,
                    claims,
                    JwtConfig.Instance.NotBefore,
                    JwtConfig.Instance.Expiration,
                    JwtConfig.Instance.SigningCredentials
                );
            var token = new JwtSecurityTokenHandler().WriteToken(jwtSecurityToken);
            token = "Bearer " + token;
            return token;
        }
        /// <summary>
        /// UserModel类Token
        /// </summary>
        /// <param name="user"></param>
        /// <returns></returns>
        public static string GetJwtToken(JwtUserModel user)
        {
            var claims = new List<Claim>() {
                new Claim("UserId",user.UserId.ToString()),
                new Claim("UserName",user.UserName),
                new Claim("UserType",user.UserType.ToString()),
            };
            return GetJwtToken(claims);
        }

        /// <summary>
        /// 解析得到User
        /// </summary>
        /// <param name="request"></param>
        /// <returns></returns>
        public static JwtUserModel DecodeToUser(HttpRequest request)
        {
            var claims = DecodeToken(request);
            var user = GetUser(claims);
            return user;
        }
        /// <summary>
        /// 解析得到User
        /// </summary>
        /// <param name="token"></param>
        /// <returns></returns>
        public static JwtUserModel DecodeToUser(string token)
        {
            var claims = DecodeToken(token);
            var user = GetUser(claims);
            return user;
        }
        /// <summary>
        /// 解析token
        /// </summary>
        /// <param name="request"></param>
        /// <returns></returns>
        public static IEnumerable<Claim> DecodeToken(HttpRequest request)
        {
            var authorization = request.Headers["Authorization"].ToString();
            var claims = DecodeToken(authorization);
            return claims;
        }
        /// <summary>
        /// 解析token
        /// </summary>
        /// <param name="token"></param>
        /// <returns></returns>
        private static IEnumerable<Claim> DecodeToken(string token)
        {
            //因为我们的Jwt是自带【Bearer 】这个请求头的，所以去掉前面的头
            var auth = token.Split(" ")[1];
            var handler = new JwtSecurityTokenHandler();
            //反解密，获取其中的Claims
            var payload = handler.ReadJwtToken(auth).Payload;
            var claims = payload.Claims;
            return claims;
        }
        /// <summary>
        /// 获取用户信息
        /// </summary>
        /// <param name="claims"></param>
        /// <returns></returns>
        private static JwtUserModel GetUser(IEnumerable<Claim> claims)
        {
            var user = new JwtUserModel()
            {
                UserId = claims.Where(t => t.Type == "UserId").First().Value,
                UserName = claims.Where(t => t.Type == "UserName").First().Value,
                UserType = claims.Where(t => t.Type == "UserType").First().Value
            };
            return user;
        }
    }
}
